home *** CD-ROM | disk | FTP | other *** search
/ Aminet 28 / Aminet 28 (1998)(GTI - Schatztruhe)[!][Dec 1998].iso / Aminet / util / libs / shutdown.lha / shutdown_5.3 / src / sdwarn.c < prev    next >
Encoding:
C/C++ Source or Header  |  1998-09-12  |  6.5 KB  |  304 lines

  1. /*
  2.    sdwarn.c --- example shutdown client.
  3.  
  4.    (c) Copyright 1995-98 SHW Wabnitz
  5.    Written by Bernhard Fastenrath (fasten@shw.com)
  6.  
  7.    This file may be distributed under the terms
  8.    of the GNU General Public License.
  9. */
  10.  
  11. /// Includes & Declarations
  12. #if defined (__SASC)
  13. #include <dos.h>
  14. #endif
  15. #include <stdio.h>
  16. #include <string.h>
  17. #include <stdlib.h>
  18. #include <exec/types.h>
  19. #include <proto/exec.h>
  20. #include <proto/dos.h>
  21.  
  22. #include "queue/queue.h"
  23. #include "queue/shutdown.h"
  24.  
  25. #if defined (__GNUC__)
  26. #include "queue/queue_inline.h"
  27. #elif defined (__SASC_60)
  28. #include "queue/queue_pragmas.h"
  29. #endif
  30.  
  31. void CloseTimerDevice (void);
  32. int CheckCLISession (void);
  33.  
  34. struct Library *QueueBase = NULL;
  35. struct timerequest *TimerReq = NULL;
  36. struct MsgPort *TimerPort = NULL;
  37. ULONG TimerMask = 0;
  38. ULONG QueueMask = 0;
  39. ULONG CliNumber = 0;
  40. BPTR CliStdout = NULL;
  41. struct Process *MyProc;
  42. APTR WindowPtr;
  43.  
  44. char *optarg = NULL;
  45. ///
  46.  
  47. /// getopt()
  48. int
  49. getopt (int argc, char *const *argv, const char *opts)
  50. {
  51.   static int pos = 0;
  52.   char *c;
  53.  
  54.   while (++pos < argc && argv[pos][0] != '-');
  55.   if (pos >= argc)
  56.     return -1;
  57.   if ((c = strchr (opts, (int) argv[pos][1])) == 0)
  58.     return (int) '?';
  59.   if (*(c+1) != ':')
  60.     return (int) *c;
  61.   if (strlen (argv[pos]) > 2)
  62.     optarg = argv[pos] + 2;
  63.   else if (pos+1 < argc)
  64.     optarg = argv[pos+1];
  65.   else
  66.     return (int) '?';
  67.   return (int) *c;
  68. }
  69. ///
  70.  
  71. /// CheckCLISession()
  72. int
  73. CheckCLISession (void)
  74. {
  75.   struct Process *pr;
  76.   int code = 0;
  77.  
  78.   if (!CliNumber)
  79.     return 1;
  80.  
  81.   Forbid ();
  82.   if (pr = FindCliProc (CliNumber))
  83.   {
  84.     /* We might have found a new CLI
  85.        with the same number.
  86.     */
  87.     if (pr -> pr_COS == CliStdout)
  88.       code = 1;
  89.   }
  90.   Permit ();
  91.   return code;
  92. }
  93. ///
  94.  
  95. /// CloseTimerDevice()
  96. void
  97. CloseTimerDevice (void)
  98. {
  99.   if (!TimerPort)
  100.     return;
  101.  
  102.   AbortIO ((struct IORequest *) TimerReq);
  103.   WaitIO ((struct IORequest *) TimerReq);
  104.   CloseDevice ((struct IORequest *) TimerReq);
  105.   DeleteIORequest (TimerReq);
  106.   DeleteMsgPort (TimerPort);
  107.   TimerPort = NULL;
  108. }
  109. ///
  110.  
  111. /// StartTimer()
  112. void
  113. StartTimer (void)
  114. {
  115.   if (TimerPort)
  116.   {
  117.     TimerReq -> tr_node.io_Command = TR_ADDREQUEST;
  118.     TimerReq -> tr_time.tv_secs  = 3;
  119.     TimerReq -> tr_time.tv_micro = 0;
  120.     SendIO ((struct IORequest *) TimerReq);
  121.   }
  122. }
  123. ///
  124.  
  125. /// OpenTimerDevice()
  126. ULONG
  127. OpenTimerDevice (void)
  128. {
  129.   if (!(TimerPort = CreateMsgPort ()))
  130.     return 0;
  131.  
  132.   if (!(TimerReq = (struct timerequest *)
  133.       CreateIORequest (TimerPort, sizeof (struct timerequest))))
  134.   {
  135.     DeleteMsgPort (TimerPort);
  136.     return 0;
  137.   }
  138.   if (OpenDevice (TIMERNAME, UNIT_VBLANK, (struct IORequest *) TimerReq, 0))
  139.   {
  140.     DeleteIORequest (TimerReq);
  141.     DeleteMsgPort (TimerPort);
  142.     return 0;
  143.   }
  144.   StartTimer ();
  145.   return TimerMask = 1 << TimerPort -> mp_SigBit;
  146. }
  147. ///
  148.  
  149. /// GoingDownMessage()
  150. void
  151. GoingDownMessage (int seconds)
  152. {
  153.   if (seconds / 3600)
  154.     printf ("The system is going down in %d:%.2d hours.\n",
  155.             seconds / 3600, (seconds % 3600) / 60);
  156.   else if (seconds / 60)
  157.     printf ("The system is going down in %d:%.2d minutes.\n",
  158.             seconds / 60, seconds % 60);
  159.   else
  160.     printf ("The system is going down in %d seconds.\n", seconds);
  161. }
  162. ///
  163.  
  164. /// main()
  165. int
  166. main (int argc, char *argv[])
  167. {
  168.   QMessage *qmsg, *lqmsg;
  169.   ShutdownMessage *sm;
  170.   UpsInfo *ups;
  171.   char *UpsEvents[] = UPS_EV_NAMES;
  172.   int verbose = 0;
  173.   ULONG sigbit, sigmask, rmask;
  174.   QHandle qh;
  175.   int opt;
  176.  
  177.   MyProc = (struct Process *) FindTask (0);
  178.   WindowPtr = MyProc -> pr_WindowPtr;
  179.   MyProc -> pr_WindowPtr = (void *) -1;
  180.  
  181.   while ((opt = getopt (argc, argv, "c:v")) != -1)
  182.     switch (opt)
  183.     {
  184.       case 'v': verbose = 1; break;
  185.       case 'c':
  186.         if (CliNumber = atoi (optarg))
  187.         {
  188.           struct Process *pr;
  189.  
  190.           Forbid ();
  191.           if (pr = FindCliProc (CliNumber))
  192.         CliStdout = pr -> pr_COS;
  193.           Permit ();
  194.           if (!CliStdout)
  195.           {
  196.         printf ("Invalid CLI.\n", CliNumber);
  197.         exit ( EXIT_FAILURE );
  198.           }
  199.         }
  200.     break;
  201.       default:
  202.         printf ("Usage: %s [-v] [-c <cli>].\n", argv[0]);
  203.     exit (EXIT_FAILURE);
  204.     }
  205.  
  206.   if (!(QueueBase = OpenLibrary ("queue.library", 0)))
  207.   {
  208.     printf ("Failed to open queue.library.\n");
  209.     return EXIT_FAILURE;
  210.   }
  211.   if (CliNumber)
  212.   {
  213.     if (!OpenTimerDevice ())
  214.     {
  215.       printf ("Failed to open timer.device.\n");
  216.       CloseLibrary (QueueBase);
  217.       return EXIT_FAILURE;
  218.     }
  219.   }
  220.   if ((sigbit = AllocSignal (-1)) != -1)
  221.   {
  222.     QueueMask = 1 << sigbit;
  223.     sigmask = SIGBREAKF_CTRL_C | TimerMask | QueueMask;
  224.  
  225.     if (qh = QOpen ("shutdown", QMODE_LISTEN, sigbit))
  226.     {
  227.       while (1)
  228.       {
  229.     rmask = Wait (sigmask);
  230.     if (rmask & TimerMask)
  231.       StartTimer ();
  232.  
  233.         if (rmask & QueueMask)
  234.         {
  235.       lqmsg = NULL;
  236.       while (qmsg = QGetMsg (qh))
  237.       {
  238.         sm = (ShutdownMessage *) qmsg -> qm_Data;
  239.             lqmsg = qmsg;
  240.  
  241.         switch (sm -> sm_Status)
  242.         {
  243.           case SHUTDOWN_WARN:
  244.           case SHUTDOWN_NOW:
  245.             GoingDownMessage (sm -> sm_TimeLeft);
  246.             break;
  247.           case SHUTDOWN_INFO:
  248.             if (verbose)
  249.                 {
  250.               if (sm -> sm_Info == SDMI_UPS_MONITOR)
  251.                   {
  252.                 printf ("Shutdown info received:\n");
  253.                     ups = sm -> sm_Extra;
  254.                     if (ups -> ui_Event > UPS_EV_MAX)
  255.                       printf ("Event = %d (unknown)\n", ups -> ui_Event);
  256.                     else
  257.                       printf ("Event = %s.\n", UpsEvents[ups -> ui_Event]);
  258.                 printf ("Charge = %d.\n", ups -> ui_Charge);
  259.                 printf ("Remaining time = %d.\n", ups -> ui_Time);            
  260.                   }
  261.               else
  262.                 printf ("Shutdown info received.\n");
  263.                 }
  264.             break;
  265.           case SHUTDOWN_ABORT:
  266.             printf ("Shutdown has been aborted.\n");
  267.             break;
  268.           case SHUTDOWN_UMOUNT:
  269.             printf ("The system is going down, unmounting filesystems.\n");
  270.             break;
  271.           case SHUTDOWN_HALT:
  272.             printf ("The system is halted.\n");
  273.             break;
  274.           default:
  275.             printf ("Unknown message.\n");
  276.             break;
  277.         }
  278.           }
  279.       if (lqmsg)
  280.         QReplyMsg (qh);
  281.     }
  282.         if (rmask & SIGBREAKF_CTRL_C || !CheckCLISession ())
  283.         {
  284.       if (rmask & SIGBREAKF_CTRL_C)
  285.         printf ("CTRL-C\n");
  286.       else
  287.         printf ("\n%s: End of session.\n", argv[0]);
  288.       QClose (qh);
  289.       break;
  290.         }
  291.       }
  292.     }
  293.     else
  294.       printf ("Can't open shutdown queue.\n");
  295.   }
  296.   else
  297.     printf ("Can't allocate signal.\n");
  298.   CloseTimerDevice ();
  299.   CloseLibrary (QueueBase);
  300.   MyProc -> pr_WindowPtr = WindowPtr;
  301.   exit ( EXIT_SUCCESS );
  302. }
  303. ///
  304.